From 7355824f5671ab6cf4584fe227d016f83e19b8ef Mon Sep 17 00:00:00 2001 From: "kaf24@firebug.cl.cam.ac.uk" Date: Mon, 14 Nov 2005 18:13:38 +0100 Subject: [PATCH] Use make_lowmem_page_readonly/writable() in preference to the generic functions where appropriate. This prevents us using the generic functions early during boot, when pte_pfn() does not work (because max_mapnr is not initialised). Signed-off-by: Keir Fraser --- .../arch/xen/i386/kernel/cpu/common.c | 2 +- linux-2.6-xen-sparse/arch/xen/i386/mm/init.c | 4 ++-- linux-2.6-xen-sparse/arch/xen/i386/mm/pgtable.c | 15 +++++++-------- xen/arch/x86/mm.c | 14 ++++++++++---- 4 files changed, 20 insertions(+), 15 deletions(-) diff --git a/linux-2.6-xen-sparse/arch/xen/i386/kernel/cpu/common.c b/linux-2.6-xen-sparse/arch/xen/i386/kernel/cpu/common.c index 8a718ea36b..af44ca70f0 100644 --- a/linux-2.6-xen-sparse/arch/xen/i386/kernel/cpu/common.c +++ b/linux-2.6-xen-sparse/arch/xen/i386/kernel/cpu/common.c @@ -572,7 +572,7 @@ void __cpuinit cpu_gdt_init(struct Xgt_desc_struct *gdt_descr) va < gdt_descr->address + gdt_descr->size; va += PAGE_SIZE, f++) { frames[f] = virt_to_mfn(va); - make_page_readonly((void *)va); + make_lowmem_page_readonly((void *)va); } if (HYPERVISOR_set_gdt(frames, gdt_descr->size / 8)) BUG(); diff --git a/linux-2.6-xen-sparse/arch/xen/i386/mm/init.c b/linux-2.6-xen-sparse/arch/xen/i386/mm/init.c index bed3831a23..4f73ca4e94 100644 --- a/linux-2.6-xen-sparse/arch/xen/i386/mm/init.c +++ b/linux-2.6-xen-sparse/arch/xen/i386/mm/init.c @@ -68,7 +68,7 @@ static pmd_t * __init one_md_table_init(pgd_t *pgd) #ifdef CONFIG_X86_PAE pmd_table = (pmd_t *) alloc_bootmem_low_pages(PAGE_SIZE); - make_page_readonly(pmd_table); + make_lowmem_page_readonly(pmd_table); set_pgd(pgd, __pgd(__pa(pmd_table) | _PAGE_PRESENT)); pud = pud_offset(pgd, 0); if (pmd_table != pmd_offset(pud, 0)) @@ -89,7 +89,7 @@ static pte_t * __init one_page_table_init(pmd_t *pmd) { if (pmd_none(*pmd)) { pte_t *page_table = (pte_t *) alloc_bootmem_low_pages(PAGE_SIZE); - make_page_readonly(page_table); + make_lowmem_page_readonly(page_table); set_pmd(pmd, __pmd(__pa(page_table) | _PAGE_TABLE)); if (page_table != pte_offset_kernel(pmd, 0)) BUG(); diff --git a/linux-2.6-xen-sparse/arch/xen/i386/mm/pgtable.c b/linux-2.6-xen-sparse/arch/xen/i386/mm/pgtable.c index 05987d5e38..e7fbddcb05 100644 --- a/linux-2.6-xen-sparse/arch/xen/i386/mm/pgtable.c +++ b/linux-2.6-xen-sparse/arch/xen/i386/mm/pgtable.c @@ -199,7 +199,7 @@ pte_t *pte_alloc_one_kernel(struct mm_struct *mm, unsigned long address) { pte_t *pte = (pte_t *)__get_free_page(GFP_KERNEL|__GFP_REPEAT|__GFP_ZERO); if (pte) - make_page_readonly(pte); + make_lowmem_page_readonly(pte); return pte; } @@ -336,7 +336,7 @@ pgd_t *pgd_alloc(struct mm_struct *mm) spin_lock_irqsave(&pgd_lock, flags); memcpy(pmd, copy_pmd, PAGE_SIZE); spin_unlock_irqrestore(&pgd_lock, flags); - make_page_readonly(pmd); + make_lowmem_page_readonly(pmd); set_pgd(&pgd[USER_PTRS_PER_PGD], __pgd(1 + __pa(pmd))); } @@ -367,12 +367,12 @@ void pgd_free(pgd_t *pgd) if (PTRS_PER_PMD > 1) { for (i = 0; i < USER_PTRS_PER_PGD; ++i) { pmd_t *pmd = (void *)__va(pgd_val(pgd[i])-1); - make_page_writable(pmd); + make_lowmem_page_writable(pmd); kmem_cache_free(pmd_cache, pmd); } if (!HAVE_SHARED_KERNEL_PMD) { pmd_t *pmd = (void *)__va(pgd_val(pgd[USER_PTRS_PER_PGD])-1); - make_page_writable(pmd); + make_lowmem_page_writable(pmd); memset(pmd, 0, PTRS_PER_PMD*sizeof(pmd_t)); kmem_cache_free(pmd_cache, pmd); } @@ -382,6 +382,7 @@ void pgd_free(pgd_t *pgd) } #ifndef CONFIG_XEN_SHADOW_MODE +asmlinkage int xprintk(const char *fmt, ...); void make_lowmem_page_readonly(void *va) { pte_t *pte = virt_to_ptep(va); @@ -399,8 +400,7 @@ void make_page_readonly(void *va) pte_t *pte = virt_to_ptep(va); set_pte(pte, pte_wrprotect(*pte)); if ((unsigned long)va >= (unsigned long)high_memory) { - unsigned long pfn; - pfn = pte_pfn(*pte); + unsigned long pfn = pte_pfn(*pte); #ifdef CONFIG_HIGHMEM if (pfn < highstart_pfn) #endif @@ -414,8 +414,7 @@ void make_page_writable(void *va) pte_t *pte = virt_to_ptep(va); set_pte(pte, pte_mkwrite(*pte)); if ((unsigned long)va >= (unsigned long)high_memory) { - unsigned long pfn; - pfn = pte_pfn(*pte); + unsigned long pfn = pte_pfn(*pte); #ifdef CONFIG_HIGHMEM if (pfn < highstart_pfn) #endif diff --git a/xen/arch/x86/mm.c b/xen/arch/x86/mm.c index a85b5fa52c..b37a16a4b0 100644 --- a/xen/arch/x86/mm.c +++ b/xen/arch/x86/mm.c @@ -3125,7 +3125,10 @@ static int ptwr_emulated_update( /* Check the new PTE. */ nl1e = l1e_from_intpte(val); if ( unlikely(!get_page_from_l1e(nl1e, d)) ) + { + MEM_LOG("ptwr_emulate: could not get_page_from_l1e()"); return X86EMUL_UNHANDLEABLE; + } /* Checked successfully: do the update (write or cmpxchg). */ pl1e = map_domain_page(page_to_pfn(page)); @@ -3248,6 +3251,9 @@ int ptwr_do_page_fault(struct domain *d, unsigned long addr, goto emulate; #endif + PTWR_PRINTK("ptwr_page_fault on l1 pt at va %lx, pfn %lx, eip %lx\n", + addr, pfn, (unsigned long)regs->eip); + /* Get the L2 index at which this L1 p.t. is always mapped. */ l2_idx = page->u.inuse.type_info & PGT_va_mask; if ( unlikely(l2_idx >= PGT_va_unknown) ) @@ -3292,10 +3298,6 @@ int ptwr_do_page_fault(struct domain *d, unsigned long addr, goto emulate; } - PTWR_PRINTK("[%c] page_fault on l1 pt at va %lx, pt for %08lx, " - "pfn %lx\n", PTWR_PRINT_WHICH, - addr, l2_idx << L2_PAGETABLE_SHIFT, pfn); - /* * We only allow one ACTIVE and one INACTIVE p.t. to be updated at at * time. If there is already one, we must flush it out. @@ -3314,6 +3316,10 @@ int ptwr_do_page_fault(struct domain *d, unsigned long addr, goto emulate; } + PTWR_PRINTK("[%c] batched ptwr_page_fault at va %lx, pt for %08lx, " + "pfn %lx\n", PTWR_PRINT_WHICH, addr, + l2_idx << L2_PAGETABLE_SHIFT, pfn); + d->arch.ptwr[which].l1va = addr | 1; d->arch.ptwr[which].l2_idx = l2_idx; d->arch.ptwr[which].vcpu = current; -- 2.30.2